﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Text;
using System.Xml;

namespace HandScreen.DataMining
{
    public class RSSManager : IDisposable
    {
        private String _url;
        private String _feedTitle;
        private String _feedDescription;
        private Collection<Rss.Items> _rssItems = new Collection<Rss.Items>();
        private bool isDisposed;

        #region Constructors

        public RSSManager()
        {
            _url = String.Empty;
        }

        public RSSManager(String feedUrl)
        {
            _url = feedUrl;
        }

        #endregion

        #region Properties

        public String Url
        {
            get { return _url; }
            set { _url = value; }
        }

        public Collection<Rss.Items> RSSItems
        {
            get { return _rssItems; }
        }

        public String FeedTitle
        {
            get { return _feedTitle; }
        }

        public String FeedDescription
        {
            get { return _feedDescription; }
        }

        #endregion

        #region Methods

        public Collection<Rss.Items> GetRSSFeed()
        {
            if (String.IsNullOrEmpty(Url))
            {
                throw new ArgumentException("Needs a feed URL");
            }

            using (XmlReader reader = XmlReader.Create(Url))
            {
                XmlDocument xmlDoc = new XmlDocument();
                xmlDoc.Load(reader);
                ParseDocElements(xmlDoc.SelectSingleNode("//channel"), "title", ref _feedTitle);
                ParseDocElements(xmlDoc.SelectSingleNode("//channel"), "description", ref _feedDescription);
                ParseRssItems(xmlDoc);
                return _rssItems;
            }
        }

        private void ParseRssItems(XmlDocument xmlDoc)
        {
            _rssItems.Clear();
            XmlNodeList nodes = xmlDoc.SelectNodes("rss/channel/item");

            foreach (XmlNode node in nodes)
            {
                Rss.Items item = new Rss.Items();
                ParseDocElements(node, "title", ref item.Title);
                ParseDocElements(node, "description", ref item.Description);
                ParseDocElements(node, "link", ref item.Link);
                String date = null;
                ParseDocElements(node, "pubDate", ref date);
                DateTime.TryParse(date, out item.Date);
                _rssItems.Add(item);

            }
        }

        private void ParseDocElements(XmlNode parent, string xPath, ref string property)
        {
            XmlNode node = parent.SelectSingleNode(xPath);

            if (node != null)
            {
                property = node.InnerText;
            }
            else
            {
                property = "Unresolvable";
            }
        }

        #endregion

        #region Disposable

        private void Dispose(bool disposing)
        {
            if (disposing && !isDisposed)
            {
                _rssItems.Clear();
                _url = null;
                _feedTitle = null;
                _feedDescription = null;
            }

            isDisposed = true;
        }

        public void Dispose()
        {
            Dispose(true);
            GC.SuppressFinalize(this);
        }

        #endregion

    }
}
